package com.xgp.company.tool;

import com.xgp.company.annotaion.MyField;
import com.xgp.company.annotaion.MyTable;
import com.xgp.company.annotaion.Plan;
import com.xgp.company.model.User;

import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.sql.Connection;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@SuppressWarnings("all")
public class CreateTable {
    //获取数据库连接对象
    private static Connection con = JDBCUtilsConfig.getConnection();

    public static void create(String pack)  {
        List<String> lists = ClazzUtils.getClazzName("com.xgp.company.model", true);

        for (String list : lists) {
            String newpack = pack + list.substring(list.lastIndexOf('.'));
//            System.out.println(newpack);
            Class<?> clazz = null;
            try {
                clazz = Class.forName(newpack);
            } catch (ClassNotFoundException e) {
                e.printStackTrace();
            }
            if(flag(clazz))
                init(clazz);
        }
    }

    private static boolean flag(Class clazz) {
        //通过反射获取MyTable注解
        //获得注解的value的值
        MyTable table = (MyTable) clazz.getAnnotation(MyTable.class);
        if(table == null) return false;
        return true;
    }

    private static void  init(Class clazz) {

//        Class<User> clazz = User.class;

        String tableName = getTableName(clazz);
        List<Map<String, String>> filelds = null;
        filelds = getFilelds(clazz);

/*        for (Map<String, String> fileld : filelds) {
            for (String s : fileld.keySet()) {
                System.out.println(s + " === " + fileld.get(s));
            }
        }*/

        // 拼接sql语句
        String sqlTitle = "CREATE TABLE IF NOT EXISTS " + tableName + "(";

        String sql = sqlTitle;
        for (Map<String, String> fileld : filelds) {
            String def = fileld.get("def");
            if("VARCHAR".equals(fileld.get("type"))) {
                def = "DEFAULT" + " " +"'" + def + "'";
            }else if("PRIMARY KEY AUTO_INCREMENT".equals(fileld.get("plan")) || "PRIMARY KEY".equals(fileld.get("plan"))) {
                def = "";
            }else {
                def = "DEFAULT" + " " + def;
            }
            String sqlBody = fileld.get("name") + " " + fileld.get("type") + "(" + fileld.get("len") + ")" + " " + fileld.get("plan") + " " + def + " " + "COMMENT" + " '" + fileld.get("comment") + "',";

            sql = sql + sqlBody;
        }
        sql = sql.substring(0,sql.length() - 1) + ")ENGINE=INNODB DEFAULT CHARSET = 'utf8'";
//        System.out.println(sql);

        //执行sql语句
        Statement stmt = null;
        try {
            stmt = con.createStatement();
        } catch (SQLException e) {
            e.printStackTrace();
        }
        try {
            stmt.executeUpdate(sql);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        try {
            stmt.close();
        } catch (SQLException e) {
            e.printStackTrace();
        }
        System.out.println(tableName + "数据表创建成功");
    }


    private static List<Map<String,String>> getFilelds(Class clazz){
        //获取类上的字段
        Field[] fields = clazz.getDeclaredFields();
        List<Map<String,String>> list = new ArrayList();
        for (Field field : fields) {
            MyField ano = field.getAnnotation(MyField.class);

            Map<String,String> map = new HashMap<>();

            String name = ano.name();   // 字段名称
            if(name.isEmpty()) name = field.getName();
            map.put("name",name); // 存字段名称
            int len = ano.len(); // 长度
            map.put("len",len + "");//存字段长度
            Plan plan = ano.plan(); //计划方案

            //分析计划
            switch (plan) {
                case PK: map.put("plan","PRIMARY KEY");break;
                case PK_AUTO:map.put("plan","PRIMARY KEY AUTO_INCREMENT");break;
                case NOT_NULL:map.put("plan","NOT NULL");break;
                case NULL:map.put("plan","NULL");break;
            }

            String comment = ano.Comment();//字段备注
            map.put("comment",comment);     //存备注

            //获取字段类型
            String type = field.getGenericType().getTypeName();
            if ("int".equals(type)) {
                map.put("type","INT");
            }else if("java.lang.String".equals(type)) {
                map.put("type","VARCHAR");
            }
            //获取默认值
            Object user = null;
            try {
                user = clazz.newInstance();
            } catch (InstantiationException e) {
                e.printStackTrace();
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }
            Method getxxx = null;
            try {
                getxxx = clazz.getMethod("get" + name.substring(0, 1).toUpperCase() + name.substring(1));
            } catch (NoSuchMethodException e) {
                e.printStackTrace();
            }
            Object res = null;
            try {
                res = getxxx.invoke(user);
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            } catch (InvocationTargetException e) {
                e.printStackTrace();
            }
            String def = "";
            if(res != null) def = res + "";
//            System.out.println(res);
            map.put("def",def);
            //存入外部集合
            list.add(map);
        }

        return list;
    }

    private static String getTableName(Class clazz) {
        //通过反射获取MyTable注解
        //获得注解的value的值
        MyTable table = (MyTable) clazz.getAnnotation(MyTable.class);
        String tableName  = table.value();

        //创建表
        if(tableName .isEmpty())
            //获取类类名,用户没有自己定义就默认为表名
            tableName = clazz.getSimpleName();

        return tableName;
    }
}
